package com.diligent.cloud.sfc.resources.impl;

import com.canny.commons.model.Codes;
import com.canny.commons.model.ListResult;
import com.canny.commons.model.ObjectResult;
import com.canny.commons.model.Result;
import com.canny.commons.page.IPage;
import com.canny.commons.page.Pagination;
import com.diligent.cloud.logistics.container.enums.BoxFillDocStatus;
import com.diligent.cloud.logistics.container.enums.BoxStatus;
import com.diligent.cloud.logistics.container.model.*;
import com.diligent.cloud.logistics.container.service.LcmBoxFillDetailFeignService;
import com.diligent.cloud.logistics.container.service.LcmBoxFillMasterFeignService;
import com.diligent.cloud.logistics.container.service.LcmBoxLedgerFeignService;
import com.diligent.cloud.logistics.container.service.LcmBoxMatFeignService;
import com.diligent.cloud.primary.data.model.rt.RtWorkCenter;
import com.diligent.cloud.sfc.model.LotsInfoAndInitiateTransport;
import com.diligent.cloud.sfc.model.MatType;
import com.diligent.cloud.sfc.model.params.inventory.AddAluminumStickInventoryParams;
import com.diligent.cloud.sfc.resources.WorkShopExtrusionResource;
import com.diligent.cloud.sfc.service.ISfcService;
import com.diligent.cloud.sfc.service.WorkShopExtrusionService;
import com.diligent.cloud.sfc.service.WorkshopSceneSprayingProcessService;
import com.diligent.cloud.sfc.service.WorkshopTransportService;
import com.diligent.cloud.web.model.PageAndCondition;
import com.diligent.cloud.web.resource.impl.AbstractActionResourceImpl;
import com.diligent.cloud.wip.core.feign.service.WipStorageFeginService;
import com.diligent.cloud.wip.core.vo.GuideMaster;
import com.diligent.cloud.workorder.model.WoLots;
import com.diligent.cloud.workorder.service.WoOrderFeignService;
import com.diligent.foundation.data.model.v2.Condition;
import org.springframework.http.HttpMethod;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.RestController;

import java.security.Principal;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;

/**
 * WorkShopExtrusionResourceImpl class
 *
 * @author xf107278
 * @date 4/24/2020
 */
@RestController
public class WorkShopExtrusionResourceImpl extends AbstractActionResourceImpl implements WorkShopExtrusionResource {
    private WorkShopExtrusionService workShopExtrusionService;
    private final WorkshopSceneSprayingProcessService workshopSceneSprayingProcessService;
    private final WorkshopTransportService workshopTransportService;
    private final ISfcService sfcService;
    private final LcmBoxLedgerFeignService lcmBoxLedgerFeignService;
    private final WoOrderFeignService orderFeignService;
    private final LcmBoxFillDetailFeignService lcmBoxFillDetailFeignService;
    private final LcmBoxMatFeignService lcmBoxMatFeignService;
    private final LcmBoxFillMasterFeignService lcmBoxFillMasterFeignService;
    private final WipStorageFeginService wipStorageFeginService;


    public WorkShopExtrusionResourceImpl(WorkShopExtrusionService workShopExtrusionService,
                                         WorkshopSceneSprayingProcessService workshopSceneSprayingProcessService,
                                         WorkshopTransportService workshopTransportService, ISfcService sfcService,
                                         LcmBoxLedgerFeignService lcmBoxLedgerFeignService,
                                         WoOrderFeignService orderFeignService,
                                         LcmBoxFillDetailFeignService lcmBoxFillDetailFeignService,
                                         LcmBoxMatFeignService lcmBoxMatFeignService,
                                         LcmBoxFillMasterFeignService lcmBoxFillMasterFeignService,
                                         WipStorageFeginService wipStorageFeginService) {
        this.workShopExtrusionService = workShopExtrusionService;
        this.workshopSceneSprayingProcessService = workshopSceneSprayingProcessService;
        this.workshopTransportService = workshopTransportService;
        this.sfcService = sfcService;
        this.lcmBoxLedgerFeignService = lcmBoxLedgerFeignService;
        this.orderFeignService = orderFeignService;
        this.lcmBoxFillDetailFeignService = lcmBoxFillDetailFeignService;
        this.lcmBoxMatFeignService = lcmBoxMatFeignService;
        this.lcmBoxFillMasterFeignService = lcmBoxFillMasterFeignService;
        this.wipStorageFeginService = wipStorageFeginService;
        init();
    }

    @Override
    public ResponseEntity<ObjectResult> selectById(Long id) {
        return null;
    }

    private void init() {
        super.registerAction(HttpMethod.POST.toString(), "addAluminumStickInventory",
                AddAluminumStickInventoryParams.class, (var1, var2, var3) -> {

                    return workShopExtrusionService.addAluminumStickInventory(var3.getAluminumStickInventoryParams(),
                            var3.getPrincipal());
                });
    }


    @Override
    public ResponseEntity<ListResult> boxReportedFilter(String machCode, String orderId, Boolean isHanging) {
        return ResponseEntity.ok(workShopExtrusionService.boxReportedFilter(machCode, orderId, isHanging));
    }

    @Override
    public ResponseEntity<ObjectResult> userBox(Long boxId, Principal principal) {
        return ResponseEntity.ok(workShopExtrusionService.userBox(boxId, principal));
    }

    @Override
    public ResponseEntity<ObjectResult> cancelUseBox(Long boxFillMasterId, Principal principal) {
        return workShopExtrusionService.cancelUseBox(boxFillMasterId, principal);
    }

    @Override
    public ResponseEntity<ListResult> matStock(String machCode, String type, Long pageIndex, Long pageSize) {
        return workShopExtrusionService.matStock(machCode, type, pageIndex, pageSize);
    }

    @Override
    public ResponseEntity<ListResult> warmingMdFilter(String machCode, Long pageIndex, Long pageSize) {
        return workShopExtrusionService.warmingMatFilter(machCode, pageIndex, pageSize, MatType.模具);
    }

    @Override
    public ResponseEntity<ListResult> upAsFilter(String machCode, Long pageIndex, Long pageSize) {
        return workShopExtrusionService.warmingMatFilter(machCode, pageIndex, pageSize, MatType.铝棒);
    }

    @Override
    public ResponseEntity<ObjectResult> getLotsInfoAndInitiateTransport(String lotCode, String location, Boolean enter,
                                                                        Principal principal) {
        ResponseEntity<ObjectResult<WoLots>> lotsInfo = workshopSceneSprayingProcessService.getLotsInfo(lotCode);
        ObjectResult result;
        if (lotsInfo.getBody().getData() == null) {
            result = new ObjectResult();
            result.modifyCode(Codes.fail.getCode(), String.format("查询不到此[%s]扎号", lotCode));
            return ResponseEntity.ok(result);
        }
        PageAndCondition pageAndCondition = new PageAndCondition();

        pageAndCondition.setPagination(new Pagination(1L, 1L));
        pageAndCondition.setConditions(Collections.singletonList(new Condition("lotCode", "eq", lotCode, null)));
        //查询当前框
        ResponseEntity<com.diligent.cloud.primary.data.model.Result<IPage<LcmBoxMat>>> lcmBoxMatPage =
                lcmBoxMatFeignService.page(pageAndCondition);
        if (lcmBoxMatPage.getBody().getData().getRecords().size() == 0) {
            result = new ObjectResult();
            result.modifyCode(Codes.fail.getCode(), String.format("查询不到此[%s]扎物料信息", lotCode));
            return ResponseEntity.ok(result);
        }

        LcmBoxMat lcmBoxMat = lcmBoxMatPage.getBody().getData().getRecords().stream().findFirst().get();
        pageAndCondition.setConditions(Collections.singletonList(new Condition("boxId", "eq", lcmBoxMat.getBoxId(),
                null)));
        pageAndCondition.setPagination(new Pagination(1L, 100L));
        ResponseEntity<com.diligent.cloud.primary.data.model.Result<IPage<LcmBoxMat>>> sameBoxByBoxIdPage =
                lcmBoxMatFeignService.page(pageAndCondition);


        LcmTransportDetail lcmTransportDetail = new LcmTransportDetail();
        Boolean error = setLcmTransportDetailBaseInfo(enter,lcmTransportDetail, lotsInfo.getBody().getData());
        if (error) {
            result = new ObjectResult();
            result.modifyCode(Codes.fail.getCode(), String.format("无法查询到此【%s】容器有效台账",
                    lotsInfo.getBody().getData().getBoxCode()));
            return ResponseEntity.ok(result);
        }
        //查询到同一框得所有扎
        List<LcmTransportDetail> lcmTransportDetails = new ArrayList<>();
        List<LcmTransportMat> lcmTransportMats = new ArrayList<>();
        LcmTransportMat lcmTransportMat;

        for (LcmBoxMat boxMat : sameBoxByBoxIdPage.getBody().getData().getRecords()) {
            lcmTransportMat = new LcmTransportMat();
            setLcmTransportMatBaseInfo(lcmTransportMat, boxMat);
            lcmTransportDetails.add(lcmTransportDetail);
            lcmTransportMats.add(lcmTransportMat);
        }


        LcmTransport lcmTransport = new LcmTransport();
        LcmTransportMaster lcmTransportMaster = new LcmTransportMaster();
        setLcmTransportMasterBaseInfo(lcmTransportMaster, lotsInfo.getBody().getData(), location);

        lcmTransport.setLcmTransportMaster(lcmTransportMaster);
        lcmTransport.setLcmTransportDetail(lcmTransportDetails);
        lcmTransport.setLcmTransportMat(lcmTransportMats);

        ResponseEntity<Result> responseEntity = workshopTransportService.addTransport(lcmTransport, principal);
        if (responseEntity.getBody().getCode() != 0) {
            result = new ObjectResult();
            result.modifyCode(Codes.fail.getCode(), String.format("发起运输失败", null));
            try {
                throw new RuntimeException();
            } catch (RuntimeException e) {
                return ResponseEntity.ok(result);
            }
        }


        LotsInfoAndInitiateTransport lotsInfoAndInitiateTransport = new LotsInfoAndInitiateTransport();
        lotsInfoAndInitiateTransport.setBoxCode(lotsInfo.getBody().getData().getBoxCode());
        lotsInfoAndInitiateTransport.setBoxWeight(lcmTransportDetail.getWeight().toString());
        lotsInfoAndInitiateTransport.setLotNum(lcmTransportMats.size());


        return ResponseEntity.ok(new ObjectResult(lotsInfoAndInitiateTransport));
    }

    private void setLcmTransportMasterBaseInfo(LcmTransportMaster lcmTransportMaster, WoLots lots, String location) {
        RtWorkCenter workCenter = sfcService.getWorkCenterByCwocCode(lots.getCwocCode());
        lcmTransportMaster.setCwocCode(workCenter.getCwocCode());
        lcmTransportMaster.setCwocName(workCenter.getCwocName());

        lcmTransportMaster.setStorageCode(workCenter.getStorageCode());
        lcmTransportMaster.setStorageName(workCenter.getStorageName());

        workCenter = sfcService.getWorkCenterByCwocCode(location);
        lcmTransportMaster.setCwocCode2(workCenter.getCwocCode());
        lcmTransportMaster.setCwocName2(workCenter.getCwocName());

        lcmTransportMaster.setStorageCode2(workCenter.getStorageCode());
        lcmTransportMaster.setStorageName2(workCenter.getStorageName());
    }

    private Boolean setLcmTransportDetailBaseInfo(Boolean enter,LcmTransportDetail lcmTransportDetail, WoLots lots) {
        PageAndCondition pageAndCondition = new PageAndCondition();
        pageAndCondition.setPagination(new Pagination(1L, 1L));
        ArrayList<Condition> conditions = new ArrayList<>();
        conditions.add(new Condition("code", "eq", lots.getBoxCode(), null));
        conditions.add(new Condition("state", "nin", BoxStatus.SCRAP.getStatus() + "," + BoxStatus.FIX.getStatus(),
                null));
        pageAndCondition.setConditions(conditions);

        ResponseEntity<com.diligent.cloud.primary.data.model.Result> search =
                lcmBoxLedgerFeignService.search(pageAndCondition);
        if (((IPage<LcmBoxLedger>) search.getBody().getData()).getRecords().size() == 0) {
            return true;
        }
        LcmBoxLedger lcmBoxLedger =
                ((IPage<LcmBoxLedger>) search.getBody().getData()).getRecords().stream().findFirst().get();
        lcmTransportDetail.setBoxId(lcmBoxLedger.getId());
        lcmTransportDetail.setBoxCode(lcmBoxLedger.getCode());
        lcmTransportDetail.setBoxName(lcmBoxLedger.getName());
        lcmTransportDetail.setTareWeight(lcmBoxLedger.getTareWeight());
        lcmTransportDetail.setWeight(lcmBoxLedger.getWeight());
        lcmTransportDetail.setVolume(lcmBoxLedger.getVolume());

        //根据判断出仓入仓
       // addStockOrder(enter,lcmBoxLedger,lots);

        return false;
    }

    private void setLcmTransportMatBaseInfo(LcmTransportMat lcmTransportMat, LcmBoxMat boxMat) {
        lcmTransportMat.setMatCode(boxMat.getMatCode());
        lcmTransportMat.setMatName(boxMat.getMatName());
        lcmTransportMat.setLotCode(boxMat.getLotCode());
        lcmTransportMat.setWeight(boxMat.getWeight());
        lcmTransportMat.setDigit(boxMat.getDigit());
        lcmTransportMat.setBatchCode(boxMat.getBatchCode());

    }
     public void addStockOrder(Boolean enter, LcmBoxLedger lcmBoxLedger, WoLots lots) {
        RtWorkCenter workCenter = sfcService.getWorkCenterByCwocCode(lots.getCwocCode());
        PageAndCondition pageAndCondition = new PageAndCondition();
        pageAndCondition.setPagination(new Pagination(1L, 1000L));
        List<Condition> conditions = new ArrayList<>();

        conditions.add(new Condition("boxId", "eq", lcmBoxLedger.getId(), null));
        conditions.add(new Condition("isCanceled", "eq", 0, null));
        conditions.add(new Condition("isClosed", "eq", 0, null));

        if (enter) {
            conditions.add(new Condition("docType", "eq", BoxFillDocStatus.INSERT.getStatus(), null));
        } else {
            conditions.add(new Condition("docType", "eq", BoxFillDocStatus.REMOVE.getStatus(), null));
        }
        pageAndCondition.setConditions(conditions);

        ResponseEntity<com.diligent.cloud.primary.data.model.Result<IPage<LcmBoxFillMaster>>> lcmBoxFillMasterPage =
                lcmBoxFillMasterFeignService.page(pageAndCondition);

        List<LcmBoxFillDetail> lcmBoxFillDetails = new ArrayList<>();
        //一个框的多个装单/卸单
        for (LcmBoxFillMaster lcmBoxFillMaster : lcmBoxFillMasterPage.getBody().getData().getRecords()) {
            pageAndCondition.setPagination(new Pagination(1L, 1L));
            pageAndCondition.setConditions(Collections.singletonList(new Condition("masterId", "eq",
                    lcmBoxFillMaster.getId(), null)));

            ResponseEntity<com.diligent.cloud.primary.data.model.Result<IPage<LcmBoxFillDetail>>> lcmBoxFillDetailPage =
                    lcmBoxFillDetailFeignService.page(pageAndCondition);
            if (lcmBoxFillDetailPage.getBody().getData().getRecords().size() == 0) {
                continue;
            }
            lcmBoxFillDetails.add( lcmBoxFillDetailPage.getBody().getData().getRecords().stream().findFirst().get());
        }
        // TODO 如何安排库位
         GuideMaster guideMaster = sfcService.generateWipStockOrderInfo(lcmBoxLedger.getId(), 1L, null,
                 workCenter, lcmBoxFillDetails);

         ObjectResult result;
         if (enter) {
             result = wipStorageFeginService.warehouse(guideMaster);
         } else {
             result = wipStorageFeginService.undercarriage(guideMaster);
         }
         if (result.getCode()!=0){
             String error = enter==true?"入仓":"出仓";
             throw new RuntimeException(String.format("%s失败",error));
         }

    }


}
